#ifdef __WXGTK__

#include "ImppGTKNotebook.h"
#include <gtk/gtk.h>
#include <wx/imaglist.h>
#include "private.h"
#include <wx/gtk/win_gtk.h>
#include <wx/log.h>
#include "../events/NotebookPageClosedEvent.h"

class wxGtkNotebookPage: public wxObject
{

public:
    wxGtkNotebookPage()
    {
        m_image = -1;
        m_page = NULL;
        m_box = NULL;
        m_close = NULL;
    }

    wxString           m_text;
    int                m_image;
    GtkWidget         *m_page;
    GtkLabel          *m_label;
    GtkWidget         *m_box;     // in which the label and image are packed
    GtkButton         *m_close;

};

struct PageClosed{

	PageClosed(wxNotebook* book, wxWindow* closed):
		book(book),closed(closed)
	{}

	wxNotebook* book;
	wxWindow* closed;
};

extern "C" {
static void gtk_page_size_callback( GtkWidget *WXUNUSED(widget), GtkAllocation* alloc, wxWindow *win )
{
    if (g_isIdle)
        wxapp_install_idle_handler();

    // wxWindowGTK::SetSize() ignores position if parent does not have
    // m_wxwindow, and infinite sizing loop can result if position is part
    // of this check. See patch 1907189.
    if ((win->m_width == alloc->width) &&
        (win->m_height == alloc->height))
    {
        return;
    }

    win->SetSize( alloc->x, alloc->y, alloc->width, alloc->height );

    /* GTK 1.2 up to version 1.2.5 is broken so that we have to call allocate
       here in order to make repositioning after resizing to take effect. */
    if ((gtk_major_version == 1) &&
        (gtk_minor_version == 2) &&
        (gtk_micro_version < 6) &&
        (win->m_wxwindow) &&
        (GTK_WIDGET_REALIZED(win->m_wxwindow)))
    {
        gtk_widget_size_allocate( win->m_wxwindow, alloc );
    }
}

static void closeClicked(GtkWidget *widget, PageClosed* closed)
{
	Impp::NotebookPageClosedEvent event(closed->closed,Impp::EVT_NOTEBOOK_PAGE_CLOSED,closed->book->GetId());
	closed->book->AddPendingEvent(event);
	delete closed;
}
/*
static void buttonReleased(GtkWidget *widget, GdkEventButton* e, PageClosed* closed)
{
	wxLogDebug(wxT("sadassssssssssssssss"));
	if(e->button != 2){
		return;
	}

	Impp::NotebookPageClosedEvent event(closed->closed,Impp::EVT_NOTEBOOK_PAGE_CLOSED,closed->book->GetId());
	closed->book->AddPendingEvent(event);
	delete closed;
}
*/
}


namespace Impp
{

BEGIN_EVENT_TABLE(ImppGTKNotebook, wxNotebook)
	EVT_MOUSE_EVENTS(ImppGTKNotebook::OnMouse)
END_EVENT_TABLE()

ImppGTKNotebook::ImppGTKNotebook(wxWindow* parent, long id) :
	wxNotebook(parent, id)
{

}

ImppGTKNotebook::~ImppGTKNotebook()
{
}

bool ImppGTKNotebook::InsertPage( size_t position,
                             wxNotebookPage* win,
                             const wxString& text,
                             bool select,
                             int imageId )
{
    wxCHECK_MSG( m_widget != NULL, false, wxT("invalid notebook") );

    wxCHECK_MSG( win->GetParent() == this, false,
               wxT("Can't add a page whose parent is not the notebook!") );

    wxCHECK_MSG( position <= GetPageCount(), false,
                 _T("invalid page index in wxNotebookPage::InsertPage()") );

    // Hack Alert! (Part II): See above in wxInsertChildInNotebook callback
    // why this has to be done.  NOTE: using gtk_widget_unparent here does not
    // work as it seems to undo too much and will cause errors in the
    // gtk_notebook_insert_page below, so instead just clear the parent by
    // hand here.
    win->m_widget->parent = NULL;

    if (m_themeEnabled)
        win->SetThemeEnabled(true);

    GtkNotebook *notebook = GTK_NOTEBOOK(m_widget);

    wxGtkNotebookPage *nb_page = new wxGtkNotebookPage();

    if ( position == GetPageCount() )
        m_pagesData.Append( nb_page );
    else
        m_pagesData.Insert( position, nb_page );

    m_pages.Insert(win, position);

    // set the label image and text
    // this must be done before adding the page, as GetPageText
    // and GetPageImage will otherwise return wrong values in
    // the page-changed event that results from inserting the
    // first page.
    nb_page->m_image = imageId;
    nb_page->m_text = wxStripMenuCodes(text);

    nb_page->m_box = gtk_hbox_new( FALSE, 1 );
    //nb_page->m_event_box = gtk_event_box_new();
    gtk_container_set_border_width((GtkContainer*)nb_page->m_box, 0);

    g_signal_connect (win->m_widget, "size_allocate",
                      G_CALLBACK (gtk_page_size_callback), win);

    gtk_notebook_insert_page(notebook, win->m_widget, nb_page->m_box, position);

    nb_page->m_page = gtk_notebook_get_nth_page(notebook, position);

    if (imageId != -1)
    {
        wxASSERT( m_imageList != NULL );
        const wxBitmap *bmp = m_imageList->GetBitmapPtr(imageId);
        GtkWidget* pixmapwid = gtk_image_new_from_pixbuf(bmp->GetPixbuf());
        gtk_box_pack_start(GTK_BOX(nb_page->m_box), pixmapwid, FALSE, FALSE, 1/*m_padding*/);
        gtk_widget_show(pixmapwid);
    }

    /* set the label text */
    nb_page->m_label = GTK_LABEL( gtk_label_new(wxGTK_CONV(nb_page->m_text)) );
    gtk_box_pack_start( GTK_BOX(nb_page->m_box), GTK_WIDGET(nb_page->m_label), FALSE, FALSE, 0/*m_padding*/ );


    gtk_rc_parse_string("style \"SmallBitmapButton\"\n"
    "{\n"
    "GtkButton::inner_border = {0, 0, 0, 0}\n"
    "GtkButton::focus_padding = 0\n"
    "GtkButton::focus_line_width = 0\n"
    "}"
    "widget \"*.SmallBitmapButton\" style \"SmallBitmapButton\""
    );

    nb_page->m_close = GTK_BUTTON( gtk_button_new() );
    gtk_widget_set_size_request(GTK_WIDGET(nb_page->m_close),22,18);
    GtkWidget* img = gtk_image_new();
    gtk_image_set_from_stock(GTK_IMAGE(img),GTK_STOCK_CLOSE,GTK_ICON_SIZE_MENU);

    gtk_button_set_image(nb_page->m_close,img);
    gtk_button_set_relief(nb_page->m_close,GTK_RELIEF_NONE);
    gtk_widget_render_icon(GTK_WIDGET(nb_page->m_close),GTK_STOCK_CLOSE,GTK_ICON_SIZE_SMALL_TOOLBAR,NULL);
    gtk_widget_set_name (GTK_WIDGET(nb_page->m_close), "SmallBitmapButton");

    gtk_box_pack_end( GTK_BOX(nb_page->m_box), GTK_WIDGET(nb_page->m_close), FALSE, FALSE, 0/*m_padding*/ );

    g_signal_connect(nb_page->m_close, "clicked",  G_CALLBACK(closeClicked), new PageClosed(this, win));
    //g_signal_connect(nb_page->m_box, "button-release-event",  G_CALLBACK(buttonReleased), new PageClosed(this, win));

    /* apply current style */
    GtkRcStyle *style = CreateWidgetStyle();
    if ( style )
    {
        gtk_widget_modify_style(GTK_WIDGET(nb_page->m_label), style);
        gtk_rc_style_unref(style);
    }

    /* show the label */
    gtk_widget_show( GTK_WIDGET(nb_page->m_label) );
    gtk_widget_show( GTK_WIDGET(nb_page->m_close) );

    if (select && (m_pagesData.GetCount() > 1))
    {
        SetSelection( position );
    }

    InvalidateBestSize();
    return true;
}

void ImppGTKNotebook::OnMouse(wxMouseEvent & event){
	if(event.GetEventType() == wxEVT_MIDDLE_UP){
		int tab = HitTest(event.GetPosition(),NULL);
		if(tab!=wxNOT_FOUND){
			NotebookPageClosedEvent event(GetPage(tab),EVT_NOTEBOOK_PAGE_CLOSED,GetId());
			AddPendingEvent(event);
		}
	}
	event.Skip(true);

}

}

#endif
